/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package core;

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Timer;
import java.util.TimerTask;
import java.util.TreeMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import protocol.TSFile;

/**
 *
 * @author Jorge
 */
public class ThreadPool extends Thread{

    private final List<WriteThread> idle;

    private final Map<String,TSFile> currentFile = new HashMap<String,TSFile>();

    private final List<String> list= new LinkedList<String>();

   


    public ThreadPool(int size) {
        idle = new ArrayList<WriteThread>(size);
        for(int i=0; i<size;i++){
            WriteThread workerThread = new WriteThread(this);
            workerThread.setName("Worker "+i);
            idle.add(workerThread);
            workerThread.start();
        }
    }
    



    public void putJob(TSFile file,byte [] bs){
        synchronized(file){
            file.write(bs);
        }
        WriteThread thread = getWorker();
        if(thread==null){
            synchronized(list){
                list.add(file.getName());
            }
        }else{
            thread.setFile(file);
            
        }        
    }

    public void testFile(TSFile file){
        synchronized(list){
            if(list.contains(file.getName()) && file.isEmpty()){
                    list.remove(file.getName());
            }
        }
    }

    
    public void joinWorkerThreads(){
        for(WriteThread w : idle){
            try {
                w.join();
            } catch (InterruptedException ex) {
                Logger.getLogger(ThreadPool.class.getName()).log(Level.SEVERE, null, ex);
            }
        }
    }

    public WriteThread getWorker(){
        WriteThread workerThread = null;

        synchronized(idle){
            if(idle.size()>0){
               workerThread = idle.remove(0);
            }
        }
        return workerThread;
    }

    public void returnWorker(WriteThread workerThread){
        synchronized(list){
            if(list.size()!=0){
               String string =  list.remove(0);
               TSFile file = currentFile.get(string);
               if(file!=null){
                workerThread.setFile(file);
                workerThread.notify();
                return;
               }
            }
            
        }
        synchronized(idle){
            idle.add(workerThread);
       }
    }

    public void putFile(TSFile file){
       currentFile.put(file.getName(), file);
    }

    public TSFile getReadFile(int key){
        try{
            return new TSFile(key);
        }catch(IOException exception){

        }
        return null;
    }


    public void closeFile(TSFile file,boolean  commit){
        synchronized(file){
            if(file.isOpen()){
                file.close();
            }
        }
        currentFile.remove(file.getName());
        if(commit){
            File file1 = new File(".//"+file.getName());
            file1.renameTo(new File(".//"+file.getFileTag().getKey()+""));
        }else{
            File file1 = new File(".//"+file.getName());
            file1.delete();
        }
        
    }

}
